package graph.shapes;

import graph.parts.Shape;

import javax.vecmath.Vector2d;

import ogl.vecmath.Color;
import ogl.vecmath.Vector;
import ogl.vecmathimp.MatrixImp;
import additional.Vertex;

public class CubeTriangles extends Shape {
	private float el;
	private Vector middle = vec(0f,0f,0f);

	//
    //     6 ------- 7 
    //   / |       / | 
    //  3 ------- 2  | 
    //  |  |      |  | 
    //  |  5 -----|- 4 
    //  | /       | / 
    //  0 ------- 1
    //
	
	public CubeTriangles() {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		el = 0.5f;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}
	
	/**
	 * Konstruktor mit selbst definierter Kantenlänge
	 * @param el
	 */
	public CubeTriangles(float el) {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		this.el = el;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}

	/**
	 * Konstruktor mit selbst definierter Kantenlänge und selbst definietem Mittelpunkt
	 * @param el
	 * @param vector
	 */
	public CubeTriangles(float el, Vector middle) {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		this.el = el;
		this.middle = middle;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}

	private void initPoints() {
		ff = FaceForm.QUADS;
		
		Float xVer = middle.x();
		Float yVer = middle.y();
		Float zVer = middle.z();
		
		p = new Vector[]{ 
				// 0 vorne unten links
				vec(-el + xVer, -el + yVer, el + zVer), 
				// 1 vorne unten rechts
				vec(el + xVer, -el + yVer, el + zVer),
				// 2 vorne oben rechts
				vec(el + xVer, el + yVer, el + zVer), 
				// 3 vorne oben links
				vec(-el + xVer, el + yVer, el + zVer), 
				// 4 hinten unten rechts
				vec(el + xVer, -el + yVer, -el + zVer), 
				// 5 hinten unten links
				vec(-el + xVer, -el + yVer, -el + zVer),
				// 6 hinten oben links
				vec(-el + xVer, el + yVer, -el + zVer), 
				// 7 hinten oben rechts
				vec(el + xVer, el + yVer, -el + zVer) 
		};
	}

	private void initColors() {
		c = new Color[]{ 
			      col(1, 0, 0), 
			      col(1, 0, 0), 
			      col(1, 0, 0), 
			      col(1, 0, 0),
			      col(1, 1, 0), 
			      col(1, 1, 0), 
			      col(1, 1, 0), 
			      col(1, 1, 0) 
		};
	}

	private void initNormals() {
		n = new Vector[] {
			vec(0, 0, 1),
	        vec(0, 0, -1),
	        vec(1, 0, 0),
	        vec(0, 1, 0),
	        vec(-1, 0, 0),
	        vec(0, -1, 0)
		};
	}

	private void initTextureCoord() {
		t = new Vector2d[] {
			new Vector2d (1, 0),
			new Vector2d (0, 0),
			new Vector2d (0, 1),
			new Vector2d (1, 1),
		};
	}

	private void initVertices() {
		ff = FaceForm.TRIANGLES;
		//
	    //     6 ------- 7 
	    //   / |       / | 
	    //  3 ------- 2  | 
	    //  |  |      |  | 
	    //  |  5 -----|- 4 
	    //  | /       | / 
	    //  0 ------- 1
	    //
		vertices = new Vertex[] {
			    // front
				v(p[1], c[1], n[0], t[1]), 
			    v(p[2], c[2], n[0], t[2]),
			    v(p[0], c[0], n[0], t[0]), 
			    
			    v(p[0], c[0], n[0], t[0]), 
			    v(p[2], c[2], n[0], t[2]),
			    v(p[3], c[3], n[0], t[3]),
			    // back
			    v(p[4], c[4], n[1], t[0]), 
			    v(p[5], c[5], n[1], t[1]), 
			    v(p[6], c[6], n[1], t[2]), 
			    
			    v(p[4], c[4], n[1], t[0]),
			    v(p[6], c[6], n[1], t[2]),
			    v(p[7], c[7], n[1], t[3]),
			    // right
			    v(p[1], c[1], n[2], t[0]), 
			    v(p[4], c[4], n[2], t[1]), 
			    v(p[7], c[7], n[2], t[2]), 
			    
			    v(p[1], c[1], n[2], t[0]),
			    v(p[7], c[7], n[2], t[2]), 
			    v(p[2], c[2], n[2], t[3]),
			    // top
			    v(p[3], c[3], n[3], t[0]), 
			    v(p[2], c[2], n[3], t[1]), 
			    v(p[7], c[7], n[3], t[2]),
			    
			    v(p[3], c[3], n[3], t[0]),
			    v(p[7], c[7], n[3], t[2]),
			    v(p[6], c[6], n[3], t[3]),
			    // left
			    v(p[5], c[5], n[4], t[0]), 
			    v(p[0], c[0], n[4], t[1]), 
			    v(p[3], c[3], n[4], t[2]),
			    
			    v(p[5], c[5], n[4], t[0]),
			    v(p[3], c[3], n[4], t[2]),
			    v(p[6], c[6], n[4], t[3]),
			    // bottom
			    v(p[5], c[5], n[5], t[0]), 
			    v(p[4], c[4], n[5], t[1]), 
			    v(p[1], c[1], n[5], t[2]), 
			    
			    v(p[5], c[5], n[5], t[0]),
			    v(p[1], c[1], n[5], t[2]),
			    v(p[0], c[0], n[5], t[3]) 
		};
		
		initVertexData();
	}
	
}
